package br.com.jmmarca.controllers;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.DataInputStream;
import java.io.File;
import java.io.FileFilter;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.OutputStreamWriter;
import java.io.Reader;
import java.io.Writer;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.ProtocolException;
import java.net.URL;
import java.net.URLConnection;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.EmptyStackException;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import br.com.jmmarca.modelo.dao.CidadeDAO;
import br.com.jmmarca.modelo.dao.EstadoDAO;
import br.com.jmmarca.modelo.dao.GrupoDAO;
import br.com.jmmarca.modelo.dao.ParametroDAO;
import br.com.jmmarca.modelo.dao.PessoaJuridicaDAO;
import br.com.jmmarca.modelo.entidade.Cidade;
import br.com.jmmarca.modelo.entidade.Endereco;
import br.com.jmmarca.modelo.entidade.Estado;
import br.com.jmmarca.modelo.entidade.Grupo;
import br.com.jmmarca.modelo.entidade.Parametro;
import br.com.jmmarca.modelo.entidade.PessoaJuridica;
import br.com.jmmarca.modelo.entidade.Telefone;
import br.com.jmmarca.modelo.enums.EnumTipoConsulta;
import br.com.jmmarca.util.UtilGeral;

/**
 * Hello world!
 *
 */
public class JFMain {
	
	public  static List<Cidade> listaCidadesThread = new ArrayList<Cidade>();
	

	public synchronized static List<Cidade> getListaCidadesThread() {
		return listaCidadesThread;
	}

	public synchronized static void setListaCidadesThread(List<Cidade> listaCidadesThread) {
		JFMain.listaCidadesThread = listaCidadesThread;
	}

	public static void main(String[] args) throws MalformedURLException,
			FileNotFoundException, IOException {

		// try {
		// NetworkServerControl serverControl = new
		// NetworkServerControl(InetAddress.getByName("localhost"), 1527);
		// serverControl.start(new PrintWriter(System.out, true));
		// } catch (Exception ex) {
		// Logger.getLogger(GetURLContent.class.getName()).log(Level.SEVERE,
		// null, ex);
		// }

		// -grupo & pagina & grupo_concluido
		// --parametros do subgrupo
		// idgrupo=1&pagina=null&finalizado=null=1&false&tipo=guiamais
		// idgrupo=2&pagina=10&finalizado=false&tipo=guiamais
		// idgrupo=2&pagina=1&finalizado=true&tipo=guiamais
		// --parametros do subgrupo
		// idpessoa=1&finalizado=null&tipo=guiamais
		// idpessoa=1&finalizado=false&tipo=guiamais
		// idpessoa=1&finalizado=true&tipo=guiamais

		JFMain urlContent = new JFMain();
		// urlContent.limparContatos();
//		urlContent.gerarEstados();
//		urlContent.gerarCidades();
//		urlContent.gerarGrupos();
//		urlContent.gerarSubGrupos();
//		 urlContent.gerarContatos();
		//
		// urlContent.ajustar_arquivos();

		// PessoaJuridica pessoaJuridica =
		// urlContent.gerarContatosDetalhe("16394704",
		// "87","http://www.guiamais.com.br/local/coroa+de+flores+para+velorio+e+cemiterio-floriculturas-sao+paulo-sp-16394704-87");
		// pessoaJuridica = urlContent.gerarContatosDetalhe("16141831", "6");

		 List<NewThreadGerarContatos> newThreadGerarContatos = new
		 ArrayList<NewThreadGerarContatos>();
		 for (int i = 0; i < 15; i++) {
			 newThreadGerarContatos.add(urlContent.new NewThreadGerarContatos());
		 }

		System.out.println("FIM");
	}

	public void gerarEstados() {
		EstadoDAO estadoDAO = EstadoDAO.getInstance();
		if (estadoDAO.getCount() == 0) {
			try {
				estadoDAO.salvar(new Estado("AC", "Acre"));
				estadoDAO.salvar(new Estado("AL", "Alagoas"));
				estadoDAO.salvar(new Estado("AP", "Amapá"));
				estadoDAO.salvar(new Estado("AM", "Amazonas"));
				estadoDAO.salvar(new Estado("BA", "Bahia"));
				estadoDAO.salvar(new Estado("CE", "Ceará"));
				estadoDAO.salvar(new Estado("DF", "Distrito Federal"));
				estadoDAO.salvar(new Estado("ES", "Espírito Santo"));
				estadoDAO.salvar(new Estado("GO", "Goiás"));
				estadoDAO.salvar(new Estado("MA", "Maranhão"));
				estadoDAO.salvar(new Estado("MT", "Mato Grosso"));
				estadoDAO.salvar(new Estado("MS", "Mato Grosso do Sul"));
				estadoDAO.salvar(new Estado("MG", "Minas Gerais"));
				estadoDAO.salvar(new Estado("PA", "Pará"));
				estadoDAO.salvar(new Estado("PB", "Paraíba"));
				estadoDAO.salvar(new Estado("PR", "Paraná"));
				estadoDAO.salvar(new Estado("PE", "Pernambuco"));
				estadoDAO.salvar(new Estado("PI", "Piauí"));
				estadoDAO.salvar(new Estado("RJ", "Rio de Janeiro"));
				estadoDAO.salvar(new Estado("RN", "Rio Grande do Norte"));
				estadoDAO.salvar(new Estado("RS", "Rio Grande do Sul"));
				estadoDAO.salvar(new Estado("RO", "Rondônia"));
				estadoDAO.salvar(new Estado("RR", "Roraima"));
				estadoDAO.salvar(new Estado("SC", "Santa Catarina"));
				estadoDAO.salvar(new Estado("SP", "São Paulo"));
				estadoDAO.salvar(new Estado("SE", "Sergipe"));
				estadoDAO.salvar(new Estado("TO", "Tocantins"));
			} catch (Exception ex) {
				Logger.getLogger(JFMain.class.getName()).log(Level.SEVERE,
						null, ex);
			}
		}
	}

	public void gerarCidades() {
		JFMain urlContent = new JFMain();
		EstadoDAO estadoDAO = EstadoDAO.getInstance();
		List<Estado> estados = estadoDAO.listar();
		// List<Estado> estados =new ArrayList<Estado>();
		// estados.add(estadoDAO.encontrar(16));
		for (Estado estado : estados) {
			String params = estado.getUf();
			String url = "http://www.guiamais.com.br/cidades/mudar-cidade/"
					+ params;
			String html = "";
			try {
				html = urlContent.getUrl(url, EnumTipoConsulta.GUIA_MAIS + "_"
						+ params, null);
				// html =
				// urlContent.getUrl("http://www.guiamais.com.br/cidades/mudar-cidade/TO",
				// "teste_TO");
			} catch (Exception ex) {
				Logger.getLogger(JFMain.class.getName()).log(Level.SEVERE,
						null, ex);
			}

			String patternStr = "<a href=\"\\/guia\\/[^\"]+\" title=\"[^\"]+\">([^<]+)<\\/a>";
			Pattern pattern = Pattern.compile(patternStr);
			Matcher matcher = pattern.matcher(html);

			boolean b = false;
			while (b = matcher.find()) {
				if (b) {
					// System.out.println(matcher.group(1));

					String cidadeNome = matcher.group(1);
					cidadeNome = cidadeNome.toUpperCase();
					CidadeDAO cidadeDAO = CidadeDAO.getInstance();
					Cidade cidade = new Cidade();
					cidade.setDescricao(cidadeNome);
					cidade.setEstado(estado);

					if (cidadeDAO.encontrarPorDescricaoEUf(cidadeNome,
							estado.getUf()) == null) {
						try {
							cidadeDAO.salvar(cidade);
						} catch (Exception ex) {
							Logger.getLogger(JFMain.class.getName()).log(
									Level.SEVERE, null, ex);
						}
					}
				}
			}

		}
	}

	public void gerarGrupos() {
		try {
			JFMain urlContent = new JFMain();
			CidadeDAO cidadeDAO = CidadeDAO.getInstance();
			List<Cidade> cidades = new ArrayList<Cidade>();
			cidades = cidadeDAO.listar(1, 1);
			for (Cidade cidade : cidades) {
				String url = "";

				String params = URLEncoder
						.encode(cidade.getDescricao() + "-"
								+ cidade.getEstado().getUf(), "ISO-8859-1")
						.toLowerCase().toString();
				url = "http://www.guiamais.com.br/guia-de-atividades/" + params;

				// System.out.println(url);
				String html = "";

				html = urlContent.getUrl(url, EnumTipoConsulta.GUIA_MAIS + "_"
						+ params, null);

				String patternStr = "<li><a href=\"\\/guia-de-atividades\\/[^0-9]+\\-([^\"]+)\">([^<]+)<\\/a><\\/li>";
				Pattern pattern = Pattern.compile(patternStr);
				Matcher matcher = pattern.matcher(html);

				boolean b = false;
				while (b = matcher.find()) {
					if (b) {
						System.out.println(matcher.group(1));
						GrupoDAO grupoDAO = GrupoDAO.getInstance();
						String descricao = matcher.group(2);
						descricao = descricao.toUpperCase().trim();

						Grupo encontrarGrupoPorDescricao = grupoDAO
								.encontrarGrupoPorDescricao(descricao);
						if (grupoDAO.encontrarGrupoPorDescricao(descricao) == null) {

							Grupo grupo = new Grupo();

							Parametro parametro = new Parametro();
							parametro
									.setTipoConsulta(EnumTipoConsulta.GUIA_MAIS);
							parametro.setNome("codigo");
							parametro.setValor(matcher.group(1));
							parametro.setGrupo(grupo);
							List<Parametro> listParametros = new ArrayList<Parametro>();
							listParametros.add(parametro);
							grupo.setParametros(listParametros);

							grupo.setDescricao(descricao);
							grupoDAO.salvar(grupo);
						} else {
							// if
							// (encontrarGrupoPorDescricao.getParametros().isEmpty())
							// {
							// Parametro parametro = new Parametro();
							// parametro.setTipoConsulta(EnumTipoConsulta.GUIA_MAIS);
							// parametro.setNome("codigo");
							// parametro.setValor(matcher.group(1));
							// parametro.setGrupo(encontrarGrupoPorDescricao);
							// List<Parametro> listParametros = new
							// ArrayList<Parametro>();
							// listParametros.add(parametro);
							// encontrarGrupoPorDescricao.setParametros(listParametros);
							// grupoDAO.salvar(encontrarGrupoPorDescricao);
							// }
						}
					}
				}

			}
		} catch (Exception ex) {
			Logger.getLogger(JFMain.class.getName())
					.log(Level.SEVERE, null, ex);
		}
	}

	public void gerarSubGrupos() {
		try {
			JFMain urlContent = new JFMain();
			GrupoDAO grupoDAO = GrupoDAO.getInstance();
			// List<Grupo> grupos = new ArrayList<Grupo>();
			List<Grupo> grupos = grupoDAO.listarGrupos();
			// grupos.add(grupoDAO.encontrar(1));
			for (Grupo grupo : grupos) {
				String url = "";

				String codigo = null;
				if (!grupo.getParametros().isEmpty()) {
					List<Parametro> parametros = grupo.getParametros();
					codigo = parametros.get(0).getValor();
				}
				if (codigo == null) {
					throw new EmptyStackException();
				}
				// http://www.guiamais.com.br/guia-de-atividades/anapolis-go/abrasivos+ferramentas+e+soldas-35003
				String params = URLEncoder
						.encode("grupo-" + codigo, "ISO-8859-1").toLowerCase()
						.toString();
				url = "http://www.guiamais.com.br/guia-de-atividades/anapolis/"
						+ params;

				// System.out.println(url);
				String html = "";
				html = urlContent.getUrl(url, EnumTipoConsulta.GUIA_MAIS + "_"
						+ params, null);

				String patternStr = "<li><a href=\"\\/busca\\/[^\"]+\">([^<]+)<\\/a><\\/li>";
				Pattern pattern = Pattern.compile(patternStr);
				Matcher matcher = pattern.matcher(html);

				boolean b = false;
				while (b = matcher.find()) {
					if (b) {
						// System.out.println(matcher.group(1));
						String descricao = matcher.group(1).toUpperCase();
						if (grupoDAO.encontrarPorDescricaoESuperior(descricao,
								grupo) == null) {
							Grupo subGrupo = new Grupo();
							subGrupo.setDescricao(descricao.trim());
							subGrupo.setSuperior(grupo);

							grupoDAO.salvar(subGrupo);

						}
					}
				}
			}
		} catch (Exception ex) {
			Logger.getLogger(JFMain.class.getName())
					.log(Level.SEVERE, null, ex);
		}
	}

	public void ajustar_arquivos() throws FileNotFoundException, IOException {
		File dir = new File(UtilGeral.getUserDir() + "cache"
				+ UtilGeral.getFileSeparator());
		FileFilter filtro = new FileFilter() {

			public boolean accept(File arq) {
				return arq.getName().matches(".*_page_.*");
			}
		};
		File[] arquivos = dir.listFiles(filtro);
		System.out.println("total de arquivos= " + arquivos.length);
		for (File file : arquivos) {
			// remove_acentos(subgrupo.getDescricao().toLowerCase().trim().replaceAll("[\\,\\-\\.]",
			// " "))
			// String params = URLDecoder.decode(file.getName());
			String params = file.getName();

			// html = file.toString(); // Read a line of text
			FileInputStream fin = new FileInputStream(UtilGeral.getUserDir()
					+ "cache" + UtilGeral.getFileSeparator() + params);
			String html = new DataInputStream(fin).readLine();

			// Close our input stream
			fin.close();

			if (html == null) {
				System.out.println("Deletando: " + params);
				file.delete();
			} else {

				Pattern compile = Pattern
						.compile("<a href=\"[^\\?]+[^\"]+\"\\s+rel=\"nofollow\" class=\"selected\">([^<]+)<\\/a>");
				Matcher matcher = compile.matcher(html);
				boolean b = false;
				while (b = matcher.find()) {
					if (b) {
						String page = matcher.group(1);
						if (!params.equals(params.replaceAll("_page_[0-9]+",
								"_page_" + page))) {
							File newFile = new File(UtilGeral.getUserDir()
									+ "cache"
									+ UtilGeral.getFileSeparator()
									+ params.replaceAll("_page_[0-9]+",
											"_page_" + page));
							if (newFile.exists()) {
								System.out.println("Delete Duplicado: "
										+ UtilGeral.getUserDir()
										+ "cache"
										+ UtilGeral.getFileSeparator()
										+ params.replaceAll("_page_[0-9]+",
												"_page_" + page));
								file.delete();
							} else {
								System.out.println(params
										+ " => page= "
										+ params.replaceAll("_page_[0-9]+",
												"_page_" + page));
								file.renameTo(newFile);
							}
						}
					}
				}
			}

			// System.out.println(params);
		}
	}

	public void limparContatos() {
		PessoaJuridicaDAO pessoaJuridicaDAO = PessoaJuridicaDAO.getInstance();
		List<PessoaJuridica> listar = pessoaJuridicaDAO.listar();
		for (PessoaJuridica pessoaJuridica : listar) {
			try {
				pessoaJuridicaDAO.remover(pessoaJuridica.getId());
			} catch (Exception ex) {
				Logger.getLogger(JFMain.class.getName()).log(Level.SEVERE,
						null, ex);
			}
		}
		GrupoDAO grupoDAO = GrupoDAO.getInstance();
		List<Grupo> listarGrupo = grupoDAO.listar();
		for (Grupo grupo : listarGrupo) {
			try {
				grupoDAO.remover(grupo.getId());
			} catch (Exception ex) {
				Logger.getLogger(JFMain.class.getName()).log(Level.SEVERE,
						null, ex);
			}
		}
	}

	public void saveImage(String imageUrl, String destinationFile) {
		try {
			System.out.println("URL FOTO= " + imageUrl);
			File file = new File(destinationFile);

			if (!file.exists()) {
				URL url = new URL(imageUrl);

				URLConnection urlRequest = new URL(imageUrl).openConnection();
				urlRequest.setReadTimeout(9999);
				urlRequest.setRequestProperty("user-agent", "Opera/9.0");

				InputStream is = urlRequest.getInputStream();
				OutputStream os = new FileOutputStream(destinationFile);

				byte[] b = new byte[2048];
				int length;

				while ((length = is.read(b)) != -1) {
					os.write(b, 0, length);
				}

				is.close();
				os.close();
				System.out.println("Foto remote: " + destinationFile);
			} else {
				System.out.println("Foto local: " + destinationFile);
			}
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	public synchronized String getUrl(String url, String cache_name,
			String cache_extension) throws IOException {

		cache_extension = (cache_extension == null) ? "html" : cache_extension;
		StringBuilder sb = new StringBuilder();
		URLConnection urlRequest;
		String html = "";
		try {
			// save to this filename
			String fileName = UtilGeral.getUserDir() + "cache"
					+ UtilGeral.getFileSeparator() + cache_name + "."
					+ cache_extension;
			File file = new File(fileName);

			if (file.exists()) {
				long fileSizeInBytes = file.length();
				// Convert the bytes to Kilobytes (1 KB = 1024 Bytes)
				long fileSizeInKB = fileSizeInBytes / 1024;
				if (fileSizeInKB < 5) {
					file.delete();
				}
			}

			if (!file.exists()) {

				file.createNewFile();
				BufferedReader in = null;

				boolean retornoOK = false;
				String inputLine;
				do {
					try {
						urlRequest = new URL(url).openConnection();
						urlRequest.setReadTimeout(10000);
						urlRequest.setRequestProperty("Content-type",
								"text/html; charset=" + "UTF-8");
						urlRequest
								.setRequestProperty("user-agent", "Opera/9.0");
						// urlConnection.setRequestProperty("cookie",
						// "some_freaking_cookie_here");

						in = new BufferedReader(new InputStreamReader(
								urlRequest.getInputStream()));
						if ((inputLine = in.readLine()) != null) {
							retornoOK = true;
						} else {
							System.err.println("Servidor não respondendo URL: "
									+ url);
							try {
								Thread.sleep(1000);
							} catch (Exception e) {
							}
						}
					} catch (Exception e) {
						System.err.println("Error URL: " + url);
						try {
							Thread.sleep(1000);
						} catch (Exception ex) {
						}
					}
				} while (!retornoOK);

				// use FileWriter to write file
				FileWriter fw = new FileWriter(file.getAbsoluteFile());
				BufferedWriter bw = new BufferedWriter(fw);

				while ((inputLine = in.readLine()) != null) {
					sb.append(inputLine);
					bw.write(inputLine);
				}

				bw.close();
				in.close();

				FileInputStream fis = new FileInputStream(fileName);
				String html_save = new DataInputStream(fis).readLine();

				// Close our input stream
				fis.close();

				if (html_save == null || html_save.isEmpty()) {
					file.delete();
				}
				System.out.println("REMOTE URL: "+url);
				System.out.println("FILE: "+fileName);
			} else {
				FileInputStream fin = new FileInputStream(fileName);
				html = new DataInputStream(fin).readLine();

				// Close our input stream
				fin.close();

				byte ptext[] = html.getBytes("ISO-8859-1");
				html = new String(ptext, "UTF-8");
				sb.append(html);

				System.out.println("LOCAL URL: "+url);
				System.out.println("FILE: "+fileName);

			}

		} catch (Exception e) {
			e.printStackTrace();
			getUrl(url, cache_name, cache_extension);
		}

		// magicazinha que converte os encode
		html = sb.toString();
		return html;
	}

	public String remove_acentos(String passa) {
		passa = passa.replaceAll("[ÂÀÁÄÃ]", "A");
		passa = passa.replaceAll("[âãàáä]", "a");
		passa = passa.replaceAll("[ÊÈÉË]", "E");
		passa = passa.replaceAll("[êèéë]", "e");
		passa = passa.replaceAll("ÎÍÌÏ", "I");
		passa = passa.replaceAll("îíìï", "i");
		passa = passa.replaceAll("[ÔÕÒÓÖ]", "O");
		passa = passa.replaceAll("[ôõòóö]", "o");
		passa = passa.replaceAll("[ÛÙÚÜ]", "U");
		passa = passa.replaceAll("[ûúùü]", "u");
		passa = passa.replaceAll("Ç", "C");
		passa = passa.replaceAll("ç", "c");
		passa = passa.replaceAll("[ýÿ]", "y");
		passa = passa.replaceAll("Ý", "Y");
		passa = passa.replaceAll("ñ", "n");
		passa = passa.replaceAll("Ñ", "N");
		passa = passa.replaceAll("['<>\\|/]", "");
		return passa;
	}

	/**
	 * Pega as informacoes basicas da pessoa
	 */
	private void gerarContatos() {

		// <a
		// href="\/local\/([^-]+)-([^-]+)-([^-]+)-([^-]+)-([0-9]+)-([0-9]+)"\s+title="Ver
		// telefone
		// <div class="adv" id="adv_16225537_1">|(!?span
		// class="street-address">)([^<]+)</span>|<span
		// class="district">([^<]+)</span>|<span
		// class="locality">([^<]+)</span>|<span
		// class="region">([^<]+)</span>|<span
		// class="postal-code">([^<]+)</span>|<a
		// href="\/local\/([^-]+)-([^-]+)-([^-]+)-([^-]+)-([0-9]+)-([0-9]+)"\s+title="Ver
		// telefone

		try {
//			JFMain urlContent = new JFMain();
			PessoaJuridicaDAO pessoaJuridicaDAO = PessoaJuridicaDAO
					.getInstance();
			GrupoDAO grupoDAO = GrupoDAO.getInstance();
			CidadeDAO cidadeDAO = CidadeDAO.getInstance();
			ParametroDAO parametroDAO = ParametroDAO.getInstance();
			// Cidade cidade = null;
			 Grupo subgrupo = grupoDAO.encontrarGrupoPorDescricao("PRODUTOS E SERVIÇOS");

			List<Cidade> cidades = new ArrayList<Cidade>();
			cidades.addAll(cidadeDAO.listarPorUf("PR"));
			cidades.addAll(cidadeDAO.listarPorUf("RO"));
			// List<Grupo> subgrupos = new ArrayList<Grupo>();
			// subgrupos.add(grupoDAO.encontrar(21193));
			int pagina;

			for (Cidade cidade : cidades) {
				if(getListaCidadesThread().contains(cidade)){
					continue;
				}
				getListaCidadesThread().add(cidade);
				List<Grupo> subgrupos = grupoDAO.listarSubGruposNaoFinalizados(cidade);
//				for (Grupo subgrupo : subgrupos) {
					Parametro parametroGrupoUltimaPagina = parametroDAO.encontrarGrupoPaginaPorCidade(subgrupo, cidade);
					if (parametroGrupoUltimaPagina == null) {
						pagina = 1;
					} else {
						pagina = Integer.parseInt(parametroGrupoUltimaPagina
								.getValor());
					}

					StringBuilder sb = new StringBuilder();
					sb.append(remove_acentos(subgrupo.getDescricao()
							.toLowerCase().trim()
							.replaceAll("&", "and")
							.replaceAll("[\\,\\-\\.]", " ")));
					sb.append("-");
					if (cidade != null) {
						sb.append(remove_acentos(cidade.getDescricao()
								.toLowerCase().trim()
								.replaceAll("[\\,\\-\\.]", " ")));
						sb.append("-");
						sb.append(cidade.getEstado().getUf().toLowerCase()
								.trim().replaceAll("[\\,\\-\\.]", " "));
					} else {
						sb.append("brasil");
					}
					String params_novo = URLEncoder.encode(sb.toString()
							.replaceAll("[\\s]{2,}", " "));

					String url = "";
					// http://www.guiamais.com.br/guia-de-atividades/anapolis-go/abrasivos+ferramentas+e+soldas-35003
					sb = new StringBuilder();
					sb.append(remove_acentos(subgrupo.getDescricao()
							.toLowerCase().trim().replaceAll("&", "and").replaceAll("[-]", "+")));
					sb.append("-");
					if (cidade != null) {
						sb.append(remove_acentos(cidade.getDescricao()
								.toLowerCase().trim().replaceAll("[-]", "+")));
						sb.append("-");
						sb.append(cidade.getEstado().getUf().toLowerCase()
								.trim().replaceAll("[-]", "+"));
					} else {
						sb.append("brasil");
					}
					String params = URLEncoder.encode(sb.toString());

					if (pagina > 1) {
						params = params_novo + "_page_" + pagina;
						url = "http://www.guiamais.com.br/busca/" + params_novo
								+ "?sort=2&page=" + pagina;
					} else {
						url = "http://www.guiamais.com.br/busca/" + params_novo
								+ "?sort=2";
					}
					// url =
					// "http://www.guiamais.com.br/busca/produtos+medico+hospitalares-porto+velho-ro";

					boolean next = true;
					boolean current = true;
					while (next) {

						String html = "";
						html = getUrl(url, EnumTipoConsulta.GUIA_MAIS + "_"
										+ params, null);
						// ultima pagina consultada para poder continuar de onde
						// parou.
						parametroGrupoUltimaPagina = parametroDAO
								.encontrarGrupoPaginaPorCidade(subgrupo, cidade);
						if (parametroGrupoUltimaPagina == null) {
							parametroGrupoUltimaPagina = new Parametro();
						}
						parametroGrupoUltimaPagina.setGrupo(subgrupo);
						parametroGrupoUltimaPagina.setCidade(cidade);
						parametroGrupoUltimaPagina.setNome("pagina");
						parametroGrupoUltimaPagina.setValor(String.valueOf(pagina));
						parametroDAO.atualizar(parametroGrupoUltimaPagina);
						// consulta as informacoes pessoais de cada camarada
						String patternStr = "class=\"fn org\"><a href=\"/local/([^-]+)-([^-]+)-([^-]+)-([^-]+)-([0-9]+)-([0-9]+)\" title=\"([^\"]+)\"";
						Pattern pattern = Pattern.compile(patternStr);
						Matcher matcher = pattern.matcher(html);
						//
						boolean b = false;
						while (b = matcher.find()) {
							if (b) {
								String codigo = URLDecoder.decode(
										matcher.group(5), "ISO-8859-1")
										.toUpperCase();
								String sequencia = URLDecoder.decode(
										matcher.group(6), "ISO-8859-1")
										.toUpperCase();
								String nome = URLDecoder.decode(
										matcher.group(7), "ISO-8859-1")
										.toUpperCase();

								System.out.println(codigo + "-" + sequencia
										+ " - " + nome);

								String url_detalhe = "http://www.guiamais.com.br/local/"
										+ matcher.group(1)
										+ "-"
										+ matcher.group(2)
										+ "-"
										+ matcher.group(3)
										+ "-"
										+ matcher.group(4)
										+ "-"
										+ matcher.group(5)
										+ "-"
										+ matcher.group(6);
								List<Parametro> parametroList = parametroDAO
										.encontrarPessoaPorCodigoESequencia(
												codigo, sequencia);
								if (parametroList == null
										|| parametroList.size() == 0) {
									PessoaJuridica pessoaJuridica = gerarContatosDetalhe(
											codigo, sequencia, url_detalhe);
									pessoaJuridicaDAO.salvar(pessoaJuridica);
								} else {
									// PessoaJuridica pessoaJuridica =
									// gerarContatosDetalhe(codigo, sequencia,
									// url_detalhe);
									// altera pessoa
									System.out.println("Já existe: " + codigo
											+ sequencia + " - " + url_detalhe);
								}
							}
						}
						String patternProximo = "<a href=\"([^\"]+)\" rel=\"nofollow\" class=\"next\">";
						pattern = Pattern.compile(patternProximo);
						matcher = pattern.matcher(html);
						b = false;
						next = false;
						current = false;
						next = false;
						int next_page = 0;
						while (b = matcher.find()) {
							if (b) {
								parametroGrupoUltimaPagina = parametroDAO
										.encontrarGrupoPaginaPorCidade(
												subgrupo, cidade);
								int pagina_save = 0;
								if (parametroGrupoUltimaPagina == null) {
									pagina_save = Integer
											.parseInt(parametroGrupoUltimaPagina
													.getValor());
								}
								next = true;
								// url da proxima pagina
								url = "http://www.guiamais.com.br/busca/"
										+ matcher.group(1);
								Pattern pagina_atual = Pattern
										.compile("<a href=\"[^\\?]+[^\"]+\"\\s+rel=\"nofollow\" class=\"selected\">([^<]+)<\\/a>");
								Matcher matcher_pagina = pagina_atual
										.matcher(html);
								if (matcher_pagina.find()) {
									pagina = Integer.valueOf(matcher_pagina
											.group(1));
								}
								if (pagina_save > pagina) {// continua de onde
															// parou
									params = params_novo + "_page_"
											+ pagina_save;
								} else {
									params = params_novo + "_page_"
											+ (pagina + 1);// pega proxima
															// pagina
								}
							}
						}
						if (next == false) {
							Parametro parametroGrupoFinalizado = parametroDAO
									.encontrarGrupoFinalizado(subgrupo, cidade);

							if (parametroGrupoFinalizado == null) {
								parametroGrupoFinalizado = new Parametro();
							}
							parametroGrupoFinalizado.setGrupo(subgrupo);
							parametroGrupoFinalizado.setCidade(cidade);
							parametroGrupoFinalizado.setNome("finalizado");
							parametroGrupoFinalizado.setValor("1");
							parametroDAO.salvar(parametroGrupoFinalizado);
						}
					}
				}
//			}
		} catch (Exception ex) {
			Logger.getLogger(JFMain.class.getName())
					.log(Level.SEVERE, null, ex);
		}
	}

	/**
	 * Pega as informacoes basicas da pessoa
	 */
	private PessoaJuridica gerarContatosDetalhe(String codigo,
			String sequencia, String url_detalhe) {
		try {
			String url = url_detalhe;

			// http://www.guiamais.com.br/guia-de-atividades/anapolis-go/abrasivos+ferramentas+e+soldas-35003
			String params = "contato_detalhe_" + codigo + "_" + sequencia;
			// url = "http://www.guiamais.com.br/local/" + grupo.getDescricao()
			// + "-ferramentas-" + cidade.getDescricao() + "-" +
			// cidade.getEstado().getUf() + "-" + codigo + "-" + sequencia;

			String html = "";

			html = getUrl(url, EnumTipoConsulta.GUIA_MAIS + "_"
					+ params, null);

			String patternNome = "itemprop=\"name\">([^<]+)<\\/h1>";
			String patternLogradouro = "itemprop=\"streetAddress\"><a[^>]+>([^<]+)</a>[^<]+<\\/span>";
			String patternCep = "itemprop=\"postalCode\">([^<]+)<\\/span>";
			String patternBairro = "class=\"district\">([^<]+)<\\/span>";
			String patternCidade = "itemprop=\"addressLocality\">([^<]+)<\\/span>";
			String patternEstado = "itemprop=\"addressRegion\">([^<]+)<\\/span>";
			String patternTelefone = "<li class=\"tel\">\\(<a[^>]+>([^<]+)</a>\\)[\\s]+([^<]+)</li>";
			String patternTelefoneOutros = "<li class=\"tel\">([0-9\\-]+)</li>";
			String patternSite = "href=\"\\/local\\/site\\/\\?companyWebsite=([^&]+)&companyName=";
			String patternGrupo = "<span class=\"categoria\">em <a href=\"[^\"]+\">([^<]+)<\\/a>";
			String patternFoto = "<img src=\"([^\"]+)\" class=\"logo\"";

			PessoaJuridica pessoaJuridica = new PessoaJuridica();

			Pattern pattern = Pattern.compile(patternNome);
			Matcher matcher = pattern.matcher(html);
			boolean b = false;
			while (b = matcher.find()) {
				if (b) {
					pessoaJuridica.setNome(matcher.group(1).toUpperCase());
				}
			}
			Endereco endereco = new Endereco();
			CidadeDAO cidadeDAO = CidadeDAO.getInstance();

			// UF
			String uf = "";
			pattern = Pattern.compile(patternEstado);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					uf = matcher.group(1).toUpperCase();
				}
			}

			// cidade
			Cidade cidade = null;
			pattern = Pattern.compile(patternCidade);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					cidade = cidadeDAO.encontrarPorDescricaoEUf(matcher
							.group(1).toUpperCase().trim(), uf.toUpperCase()
							.trim());
				}
			}
			endereco.setCidade(cidade);

			// grupo
			Grupo grupo = null;
			GrupoDAO grupoDAO = GrupoDAO.getInstance();
			pattern = Pattern.compile(patternGrupo);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					grupo = grupoDAO.encontrarSubgrupoPorDescricao(matcher
							.group(1));
				}
			}
			pessoaJuridica.setGrupo(grupo);

			// logradouro
			pattern = Pattern.compile(patternLogradouro);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					endereco.setLogradouro(matcher.group(1).toUpperCase());
				}
			}

			// bairro
			pattern = Pattern.compile(patternBairro);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					endereco.setBairro(matcher.group(1).toUpperCase());
				}
			}

			// site
			pattern = Pattern.compile(patternSite);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					pessoaJuridica.setSite(matcher.group(1).toUpperCase());
				}
			}

			// Endereco
			pattern = Pattern.compile(patternCep);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					endereco.setCep(matcher.group(1).toUpperCase());
				}
			}

			// Telefone
			Telefone telefone = new Telefone();
			pattern = Pattern.compile(patternTelefone);
			matcher = pattern.matcher(html);
			b = false;
			while (b = matcher.find()) {
				if (b) {
					telefone.setDdd(matcher.group(1).toUpperCase());
					telefone.setNumero(matcher.group(2).toUpperCase());
				}
			}
			if (telefone.getNumero() == null || telefone.getNumero().isEmpty()) {
				pattern = Pattern.compile(patternTelefoneOutros);
				matcher = pattern.matcher(html);
				b = false;
				while (b = matcher.find()) {
					if (b) {
						telefone.setNumero(matcher.group(1).toUpperCase());
					}
				}
			}

			// Foto
			pattern = Pattern.compile(patternFoto);
			matcher = pattern.matcher(html);
			b = false;
			String url_imagem = "";
			while (b = matcher.find()) {
				if (b) {
					// foto url
					http: // images.guiamais.com.br/16141831/8.gif
					url_imagem = matcher.group(1);
					// getUrl(url_imagem, "imagens" +
					// UtilGeral.getFileSeparator() + "foto_" + codigo, "gif");
					saveImage(url_imagem,
							"cache" + UtilGeral.getFileSeparator() + "imagens"
									+ UtilGeral.getFileSeparator() + "foto_"
									+ codigo + ".gif");
				}
			}
			// Enderecos
			List<Endereco> enderecos = pessoaJuridica.getEnderecos();
			if (enderecos == null) {
				enderecos = new ArrayList<Endereco>();
			}
			endereco.setPessoa(pessoaJuridica);
			enderecos.add(endereco);
			pessoaJuridica.setEnderecos(enderecos);

			// Telefone
			List<Telefone> telefones = pessoaJuridica.getTelefones();
			if (telefones == null) {
				telefones = new ArrayList<Telefone>();
			}
			telefone.setPessoa(pessoaJuridica);
			telefones.add(telefone);
			pessoaJuridica.setTelefones(telefones);
			List<Parametro> parametros = pessoaJuridica.getParametros();
			if (parametros == null) {
				parametros = new ArrayList<Parametro>();
			}
			Parametro parametro = new Parametro();
			parametro.setNome("codigo");
			parametro.setValor(codigo + "-" + sequencia);
			parametro.setPessoa(pessoaJuridica);
			parametros.add(parametro);

			pessoaJuridica.setParametros(parametros);

			return pessoaJuridica;

		} catch (Exception ex) {
			Logger.getLogger(JFMain.class.getName())
					.log(Level.SEVERE, null, ex);
		}
		return null;
	}

	/**
	 * Sends an HTTP GET request to a url
	 *
	 * @param endpoint
	 *            - The URL of the server. (Example: "
	 *            http://www.yahoo.com/search")
	 * @param requestParameters
	 *            - all the request parameters (Example:
	 *            "param1=val1&param2=val2"). Note: This method will add the
	 *            question mark (?) to the request - DO NOT add it yourself
	 * @return - The response from the end point
	 */
	public static String sendGetRequest(String endpoint,
			String requestParameters) {
		String result = null;
		if (endpoint.startsWith("http://")) {
			// Send a GET request to the servlet
			try {
				// Send data
				String urlStr = endpoint;
				if (requestParameters != null && requestParameters.length() > 0) {
					urlStr += "?" + requestParameters;
				}
				URL url = new URL(urlStr);
				URLConnection conn = url.openConnection();

				// Get the response
				BufferedReader rd = new BufferedReader(new InputStreamReader(
						conn.getInputStream()));
				StringBuffer sb = new StringBuffer();
				String line;
				while ((line = rd.readLine()) != null) {
					sb.append(line);
				}
				rd.close();
				result = sb.toString();
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
		return result;
	}

	/**
	 * Reads data from the data reader and posts it to a server via POST
	 * request. data - The data you want to send endpoint - The server's address
	 * output - writes the server's response to output
	 *
	 * @throws Exception
	 */
	public static void postData(Reader data, URL endpoint, Writer output)
			throws Exception {
		HttpURLConnection urlc = null;
		try {
			urlc = (HttpURLConnection) endpoint.openConnection();
			try {
				urlc.setRequestMethod("POST");
			} catch (ProtocolException e) {
				throw new Exception(
						"Shouldn't happen: HttpURLConnection doesn't support POST??",
						e);
			}
			urlc.setDoOutput(true);
			urlc.setDoInput(true);
			urlc.setUseCaches(false);
			urlc.setAllowUserInteraction(false);
			urlc.setRequestProperty("Content-type", "text/xml; charset="
					+ "UTF-8");

			OutputStream out = urlc.getOutputStream();

			try {
				Writer writer = new OutputStreamWriter(out, "UTF-8");
				pipe(data, writer);
				writer.close();
			} catch (IOException e) {
				throw new Exception("IOException while posting data", e);
			} finally {
				if (out != null) {
					out.close();
				}
			}

			InputStream in = urlc.getInputStream();
			try {
				Reader reader = new InputStreamReader(in);
				pipe(reader, output);
				reader.close();
			} catch (IOException e) {
				throw new Exception("IOException while reading response", e);
			} finally {
				if (in != null) {
					in.close();
				}
			}

		} catch (IOException e) {
			throw new Exception("Connection error (is server running at "
					+ endpoint + " ?): " + e);
		} finally {
			if (urlc != null) {
				urlc.disconnect();
			}
		}
	}

	/**
	 * Pipes everything from the reader to the writer via a buffer
	 */
	private static void pipe(Reader reader, Writer writer) throws IOException {
		char[] buf = new char[1024];
		int read = 0;
		while ((read = reader.read(buf)) >= 0) {
			writer.write(buf, 0, read);
		}
		writer.flush();
	}

	// Create a new thread.
	class NewThreadGerarContatos implements Runnable {

		Thread t;

		NewThreadGerarContatos() {
			// Create a new, second thread
			t = new Thread(this, "Demo Thread");
			System.out.println("Child thread: " + t);
			t.start(); // Start the thread
		}

		// This is the entry point for the second thread.
		public void run() {
			try {
				// ajustar_arquivos();
				gerarContatos();
			} catch (Exception e) {
				System.out.println("Child interrupted.");
			}
			System.out.println("Exiting child thread.");
		}
	}
}